package system

import (
	"context"
	"encoding/json"
	"net/http"
	"slices"
	"strconv"
	"strings"

	"portal/internal/common"
	"portal/internal/errorx"
	"portal/internal/svc"
	"portal/internal/tool/auth"
	"portal/internal/types"
	"portal/model"

	"github.com/zeromicro/go-zero/core/logx"
	"github.com/zeromicro/go-zero/core/stores/redis"
)

type GetInfoLogic struct {
	logx.Logger
	ctx          context.Context
	svcCtx       *svc.ServiceContext
	accountModel model.AwAccountsModel
	userModel    model.SysUserModel
	roleModel    model.SysRoleModel
	deptModel    model.SysDeptModel
	menuModel    model.SysMenuModel
	rds          *redis.Redis
}

func NewGetInfoLogic(ctx context.Context, svcCtx *svc.ServiceContext) *GetInfoLogic {
	rds, err := redis.NewRedis(redis.RedisConf{
		Host: svcCtx.Config.Redis.Host,
		Pass: svcCtx.Config.Redis.Pass,
		Type: svcCtx.Config.Redis.Type,
	})
	if err != nil {
		logx.Errorf("redis init error: %v", err)
	}
	return &GetInfoLogic{
		Logger:       logx.WithContext(ctx),
		ctx:          ctx,
		svcCtx:       svcCtx,
		accountModel: model.NewAwAccountsModel(svcCtx.Orm),
		userModel:    model.NewSysUserModel(svcCtx.Orm),
		roleModel:    model.NewSysRoleModel(svcCtx.Orm),
		deptModel:    model.NewSysDeptModel(svcCtx.Orm),
		menuModel:    model.NewSysMenuModel(svcCtx.Orm),
		rds: rds,
	}
}

func (l *GetInfoLogic) GetInfo(req *http.Request) (resp *types.CommonResponse, err error) {
	// todo: add your logic here and delete this line
	token := req.Header.Get("authorization")
	if len(token) <= 0 {
		return nil,errorx.AuthNoFound
	}
	token,_ = strings.CutPrefix(token,common.AuthorizationPrefix) 
	authinfo,err := auth.GetAuth(l.ctx)
	if err != nil {
		return nil,errorx.Unauthorized
	}
	authid := authinfo.UserId
	// 根据UserId获取用户信息（角色、管理部门<数据过滤>以及权限信息）
	user, err := l.userModel.GetOneWithDept(l.ctx, nil, authid)
	if err != nil {
		return nil, errorx.NewBizError(500, err.Error())
	}
	// 获取到 用户对应的角色列表
	roledtos, err := l.roleModel.GetListByUserId(l.ctx, nil, authid)
	if err != nil {
		return nil, errorx.NewBizError(500, err.Error())
	}
	roleVos := make([]*types.Role,0)
	for _,val := range roledtos {
		roleVos = append(roleVos, &types.Role{
			RoleId: val.RoleId,
			RoleName: val.RoleName,
			RoleKey: val.RoleKey,
			DataScope: val.DataScope,
			Status: val.Status,
		})
	}
	dept := &types.Dept{
		DeptId: user.DeptId.Int64,
		Leader: user.Leader,
		Phone:  user.LeaderPhone,
		Email:  user.LeaderEmail,
	}

	userVo := &types.User{
		UserId:      user.UserId,
		DeptId:      strconv.Itoa(int(user.DeptId.Int64)),
		UserName:    user.UserName,
		NickName:    user.NickName,
		Avatar:      user.Avatar,
		Email:       user.Email,
		Phonenumber: user.Phonenumber,
		Sex:         user.Sex,
		Status:      user.Status,
		LoginDate:   user.LoginDate,
		UpdateTime:  user.UpdateTime,
		Dept: dept,
		Roles: roleVos,
		// DataScope: dataScope,
		// Menus: menuVo.Menus,
	}
	// 保存进redis中，用于下一次调用时获取(不一定是这个接口进行调用，也有可能是其他接口调用获取一些信息)
	byteUser,err := json.Marshal(userVo)
	if err != nil {
		return nil,errorx.NewBizError(500,err.Error())
	}
	err = l.rds.SetCtx(l.ctx,common.AuthorizationHeader + token, string(byteUser))
	if err != nil {
		logx.Error(err.Error())
		return nil,errorx.NewBizError(500,err.Error())
	}
	userVo.DataScope = nil
	return &types.CommonResponse{
		Status: 200,
		Msg:    "查询成功",
		Data:   userVo,
	}, nil
}

func menuSort(menus []*types.Menu)*types.Menu{
	// 三级目录
	slices.SortFunc(menus,func(a,b *types.Menu)int{
		return int(a.OrderNum - b.OrderNum)
	})
	m := make(map[int64]*types.Menu)
	for _,val := range menus {
		m[val.MenuId] = val
	}
	rootMenu := &types.Menu{
		MenuId: 0,
		Menus: make([]*types.Menu, 0),
	}
	m[rootMenu.MenuId] = rootMenu

	for _,val := range menus {
		val.Menus = make([]*types.Menu, 0)
	}

	for _,val := range menus {
		parentId,_ := strconv.Atoi(val.ParentId)
		m[int64(parentId)].Menus = append(m[int64(parentId)].Menus, val)
	}
	return rootMenu
}